package com.briup.utils;

import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.DateFormatUtils;
import org.apache.commons.lang3.time.DateUtils;

import java.text.ParseException;
import java.util.Calendar;

/**
 * 常用日期格式
 */
public class CalendarUtil {

    /**
     * 完整日期时间无间隔格式
     */
    public static final String LONG_FORMAT = "yyyyMMddHHmmss";
    /**
     * 日期无间隔格式
     */
    public static final String SHORT_FORMAT = "yyyyMMdd";
    /**
     * 无间隔时间格式
     */
    public static final String SHORT_FORMAT_TIME = "HHmmss";
    /**
     * 完整日期时间横线与冒号分隔格式
     */
    public static final String LONG_FORMAT_LINE = "yyyy-MM-dd HH:mm:ss";
    /**
     * 横线分隔日期格式
     */
    public static final String SHORT_FORMAT_LINE = "yyyy-MM-dd";
    /**
     * 冒号分隔时间格式
     */
    public static final String SHORT_FORMAT_TIME_COLON = "HH:mm:ss";

    public static Calendar parseCalendar(String str, String... parsePatterns) {
        Calendar cal = Calendar.getInstance();
        try {
            if (ArrayUtils.isEmpty(parsePatterns)) {
                cal.setTime(DateUtils.parseDate(str, new String[]{LONG_FORMAT_LINE}));
            } else {
                cal.setTime(DateUtils.parseDate(str, parsePatterns));
            }

        } catch (ParseException e) {
        }
        return cal;
    }

    public static String parsefomatCalendar(Calendar cal) {
        return parsefomatCalendar(cal, null);
    }

    public static String parsefomatCalendar(Calendar cal, String parsePattern) {
        if (cal == null) {
            return "";
        }
        String str = "";
        if (StringUtils.isEmpty(parsePattern)) {
            str = DateFormatUtils.format(cal, CalendarUtil.LONG_FORMAT);
        } else {
            str = DateFormatUtils.format(cal, parsePattern);
        }
        return str;
    }

    public static Calendar parseCalendar(Calendar cal, String parsePattern) {
        if (cal == null) {
            return null;
        }
        String strCal = parsefomatCalendar(cal, parsePattern);
        return parseCalendar(strCal, parsePattern);
    }

    public static Calendar getNextDay(Calendar cal) {
        cal.set(Calendar.DAY_OF_YEAR, cal.get(Calendar.DAY_OF_YEAR) + 1);
        return cal;
    }

    public static String getFormatNow() {
        return parsefomatCalendar(Calendar.getInstance(), CalendarUtil.LONG_FORMAT);
    }

    public static String getFormatNow(String parsePattern) {
        return parsefomatCalendar(Calendar.getInstance(), parsePattern);
    }

    /**
     * 获取<code>c</code>所代表的时间的当天0:0:0,0
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getBeginOfTheDay(Calendar c) {
        Calendar beginOfTheNextDay = (Calendar) c.clone();
        beginOfTheNextDay.set(Calendar.HOUR_OF_DAY, 0);
        beginOfTheNextDay.set(Calendar.MINUTE, 0);
        beginOfTheNextDay.set(Calendar.SECOND, 0);
        beginOfTheNextDay.set(Calendar.MILLISECOND, 0);
        return beginOfTheNextDay;
    }

    /**
     * 获取<code>c</code>所代表的时间的当天23:59:59,999
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getEndOfTheDay(Calendar c) {
        Calendar endOfTheDay = getBeginOfTheNextDay(c);
        endOfTheDay.add(Calendar.MILLISECOND, -1);
        return endOfTheDay;
    }

    /**
     * 获取<code>c</code>所代表的时间的后一天0:0:0,0
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getBeginOfTheNextDay(Calendar c) {
        Calendar beginOfTheNextDay = (Calendar) c.clone();
        beginOfTheNextDay.add(Calendar.DATE, 1);
        return getBeginOfTheDay(beginOfTheNextDay);
    }

    /**
     * 获取<code>c</code>所代表的时间的前一天23:59:59,999
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getEndOfPreviousDay(Calendar c) {
        Calendar endOfPreviousDay = getBeginOfTheDay(c);
        endOfPreviousDay.add(Calendar.MILLISECOND, -1);
        return endOfPreviousDay;
    }

    /**
     * 获取<code>c</code>所代表的时间的当月1日的0:0:0,0
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getBeginOfTheMonth(Calendar c) {
        Calendar beginOfTheMonth = getBeginOfTheDay(c);
        beginOfTheMonth.set(Calendar.DATE, 1);
        return beginOfTheMonth;
    }

    /**
     * 获取<code>c</code>所代表的时间的当月最后一天的23:59:59,999
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getEndOfTheMonth(Calendar c) {
        Calendar beginOfTheMonth = getBeginOfTheMonth(c);
        beginOfTheMonth.add(Calendar.MONTH, 1);
        beginOfTheMonth.add(Calendar.MILLISECOND, -1);
        return beginOfTheMonth;
    }

    /**
     * 获取<code>c</code>所代表的时间的后一月1日的0:0:0,0
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getBeginOfTheNextMonth(Calendar c) {
        Calendar beginOfTheNextMonth = (Calendar) c.clone();
        beginOfTheNextMonth.add(Calendar.MONTH, 1);
        return getBeginOfTheMonth(beginOfTheNextMonth);
    }

    /**
     * 获取<code>c</code>所代表的时间的前一月最后一天23:59:59,999
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getEndOfPreviousMonth(Calendar c) {
        Calendar endOfPreviousMonth = getBeginOfTheMonth(c);
        endOfPreviousMonth.add(Calendar.MILLISECOND, -1);
        return endOfPreviousMonth;
    }

    /**
     * 获取<code>c</code>所代表的时间的当年1月1日的0:0:0,0
     *
     * @param
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getBeginOfTheYear(Calendar calendar) {
        Calendar beginOfTheYear = getBeginOfTheDay(calendar);
        beginOfTheYear.set(Calendar.DATE, 1);
        beginOfTheYear.set(Calendar.MONTH, 0);
        return beginOfTheYear;
    }

    /**
     * 获取<code>c</code>所代表的时间的当年12月31日的23:59:59,999
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getEndOfTheYear(Calendar c) {
        Calendar beginOfTheYear = getBeginOfTheYear(c);
        beginOfTheYear.add(Calendar.YEAR, 1);
        beginOfTheYear.add(Calendar.MILLISECOND, -1);
        return beginOfTheYear;
    }

    /**
     * 获取<code>c</code>所代表的时间的后一年1月1日的0:0:0,0
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getBeginOfTheNextYear(Calendar c) {
        Calendar beginOfTheNextYear = (Calendar) c.clone();
        beginOfTheNextYear.add(Calendar.YEAR, 1);
        return getBeginOfTheMonth(beginOfTheNextYear);
    }

    /**
     * 获取<code>c</code>所代表的时间的前一年12月31日的23:59:59,999
     *
     * @param c 时间
     * @return 得到的结果，与<code>c</code>不是同一个对象
     */
    public static Calendar getEndOfPreviousYear(Calendar c) {
        Calendar endOfPreviousYear = getBeginOfTheYear(c);
        endOfPreviousYear.add(Calendar.MILLISECOND, -1);
        return endOfPreviousYear;
    }


    /**
     * 根据偏移单位偏移时间
     *
     * @param field  单位域
     * @param amount 偏移值
     * @return 日期
     */
    public static Calendar getInstance(Integer field, Integer amount) {
        Calendar calendar = Calendar.getInstance();
        calendar.add(field, amount);
        return calendar;
    }

}

